package com.xinghai.system.service.impl;


import java.rmi.ServerException;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

import com.xinghai.common.exception.ServiceException;
import com.xinghai.common.utils.DateUtils;

import com.xinghai.common.utils.StringUtils;
import com.xinghai.system.domain.QdUser;
import com.xinghai.system.domain.QdUserWallet;
import com.xinghai.system.domain.QdUserWalletLog;
import com.xinghai.system.domain.entity.WithdrawalDTO;
import com.xinghai.system.domain.entity.WithdrawalUpdateDTO;
import com.xinghai.system.service.IQdUserService;
import com.xinghai.system.service.IQdUserWalletLogService;
import com.xinghai.system.service.IQdUserWalletService;
import org.apache.ibatis.session.ExecutorType;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.transaction.annotation.Transactional;
import com.xinghai.common.constant.GenConstants;
import com.xinghai.system.mapper.QdUserWithdrawalMapper;
import com.xinghai.system.domain.QdUserWithdrawal;
import com.xinghai.system.service.IQdUserWithdrawalService;

/**
 * 用户提现记录Service业务层处理
 *
 * @author xinghai
 * @date 2024-12-04
 */
@Service
public class QdUserWithdrawalServiceImpl extends ServiceImpl<QdUserWithdrawalMapper, QdUserWithdrawal>
        implements IQdUserWithdrawalService
{

    @Autowired
    private SqlSessionFactory sqlSessionFactory;
    @Autowired
    private IQdUserWalletService userWalletService;
    @Autowired
    private IQdUserWalletLogService walletLogService;
    @Autowired
    private IQdUserService userService;
    @Autowired
    private IQdUserWithdrawalService withdrawalService;
    /**
     * 查询用户提现记录列表
     *
     * @param qdUserWithdrawal 用户提现记录
     * @return 用户提现记录集合
     */
    @Override
    public List<QdUserWithdrawal> list(QdUserWithdrawal qdUserWithdrawal) {
        QueryWrapper<QdUserWithdrawal> queryWrapper = new QueryWrapper<>();
        if (qdUserWithdrawal.getStatus()!= null  && !qdUserWithdrawal.getStatus().isEmpty()){
            queryWrapper.eq("status", qdUserWithdrawal.getStatus());
        }
        if (qdUserWithdrawal.getParams().get("beginCreateTime")!= null && !"".equals(qdUserWithdrawal.getParams().get("beginCreateTime"))
        &&qdUserWithdrawal.getParams().get("endCreateTime")!= null && !"".equals(qdUserWithdrawal.getParams().get("endCreateTime"))){
            queryWrapper.between("create_time", qdUserWithdrawal.getParams().get("beginCreateTime"),qdUserWithdrawal.getParams().get("endCreateTime"));
        }
        if (qdUserWithdrawal.getUserPhone()!= null  && !qdUserWithdrawal.getUserPhone().isEmpty()){
            queryWrapper.like("user_phone", qdUserWithdrawal.getUserPhone());
        }
        if (qdUserWithdrawal.getCreateTime()!= null ){
            queryWrapper.apply("date_format(create_time,'%Y-%m') = '" + DateUtils.dateTimeMonth(qdUserWithdrawal.getCreateTime())+"'");
        }
        if (qdUserWithdrawal.getUserName()!= null  && !qdUserWithdrawal.getUserName().isEmpty()){
            queryWrapper.like("user_name", qdUserWithdrawal.getUserName());
        }
        if (qdUserWithdrawal.getUserId()!= null){
            queryWrapper.eq("user_id", qdUserWithdrawal.getUserId());
        }
        if (qdUserWithdrawal.getStoreName()!= null  && !qdUserWithdrawal.getStoreName().isEmpty()){
            queryWrapper.like("store_name", qdUserWithdrawal.getStoreName());
        }
        if (qdUserWithdrawal.getSearch()!= null  && !qdUserWithdrawal.getSearch().isEmpty()){
            queryWrapper.and(m->m.like("user_phone", qdUserWithdrawal.getSearch()).or().like("user_name", qdUserWithdrawal.getSearch()));
        }
        if (qdUserWithdrawal.getStoreId()!= null){
            queryWrapper.eq("store_id", qdUserWithdrawal.getStoreId());
        }
        return this.list(queryWrapper);
    }

    /**
     * 删除用户提现记录信息
     * @param id 需要删除的数据ID
     * @param flag 是否是逻辑删除
     * @return 结果
     */
    @Override
    public boolean delete(Long id, boolean flag) {
        if (flag){
            QdUserWithdrawal qdUserWithdrawal = new QdUserWithdrawal();
            qdUserWithdrawal.setId(id);
            qdUserWithdrawal.setDelFlag(GenConstants.DELETE_FLAG_YES);
            return this.updateById(qdUserWithdrawal);
        }
        return this.removeById(id);
    }

    /**
     * 批量删除用户提现记录信息
     *
     * @param ids 需要删除的数据ID集合
     * @param flag 是否是逻辑删除
     * @return 结果
     */
    @Override
    @Transactional
    public boolean deleteBatch(Long[] ids, boolean flag) {
        if (flag){
            List<QdUserWithdrawal> collect = Arrays.stream(ids).map(m -> {
                QdUserWithdrawal qdUserWithdrawal = new QdUserWithdrawal();
                qdUserWithdrawal.setId(m);
                qdUserWithdrawal.setDelFlag(GenConstants.DELETE_FLAG_YES);
                return qdUserWithdrawal;
            }).collect(Collectors.toList());
            return this.updateBatchById(collect);
        }
        return this.removeByIds(Arrays.asList(ids));
    }

    /**
     * 导入用户提现记录信息
     *
     * @param list 用户提现记录信息集合
     * @return 结果
     */
    @Override
    @Transactional
    public boolean importData(List<QdUserWithdrawal> list){
        SqlSession sqlSession = sqlSessionFactory.openSession(ExecutorType.BATCH, false);
        try {
            QdUserWithdrawalMapper qdUserWithdrawalMapper = sqlSession.getMapper(QdUserWithdrawalMapper.class);
            list.forEach(qdUserWithdrawalMapper::insert);
            // 提交数据
            sqlSession.commit();
            sqlSession.rollback();
        } catch (Exception e) {
            sqlSession.rollback();
            return false;
        } finally {
            sqlSession.close();
        }
        return true;
    }

    @Override
    @Transactional
    public boolean withdrawal(WithdrawalDTO withdrawalDTO) {
        //余额减少
        QdUserWallet qdUserWallet = userWalletService.getByUserId(withdrawalDTO.getUserId());
        if(qdUserWallet.getWithdrawalWallet().compareTo(withdrawalDTO.getMoney())<0){
            throw new ServiceException("余额不足");
        }
        QdUserWallet wallet = new QdUserWallet();
        wallet.setId(qdUserWallet.getId());
        wallet.setWithdrawalWallet(qdUserWallet.getWithdrawalWallet().subtract(withdrawalDTO.getMoney()));
        wallet.setFrozenWallet(qdUserWallet.getFrozenWallet().add(withdrawalDTO.getMoney()));
        userWalletService.updateById(wallet);
        //增加日志
        QdUserWalletLog qdUserWalletLog = new QdUserWalletLog();
        qdUserWalletLog.setUserId(Long.valueOf(withdrawalDTO.getUserId()));
        qdUserWalletLog.setChangeAmount(withdrawalDTO.getMoney());
        qdUserWalletLog.setType("2");
        qdUserWalletLog.setDetail("提现申请");
        walletLogService.save(qdUserWalletLog);

        QdUser user = userService.getById(withdrawalDTO.getUserId());
        //增加记录
        QdUserWithdrawal qdUserWithdrawal = new QdUserWithdrawal();
        qdUserWithdrawal.setUserId(Long.valueOf(withdrawalDTO.getUserId()));
        qdUserWithdrawal.setWithdrawalAmount(withdrawalDTO.getMoney());
        qdUserWithdrawal.setStatus("0");
        qdUserWithdrawal.setUserPhone(user.getUserPhone());
        qdUserWithdrawal.setUserName(user.getNickName());
        qdUserWithdrawal.setStoreId(user.getAscriptionStore());
        qdUserWithdrawal.setStoreName(user.getStoreName());
        return this.save(qdUserWithdrawal);
    }

    @Override
    @Transactional
    public boolean updateStatus(WithdrawalUpdateDTO dto) {
        String[] strings = dto.getIds().split(",");
        //审核通过
        //余额从冻结到已提现
        if ("1".equals(dto.getStatus())){
            Arrays.stream(strings).forEach(m->{
                QdUserWithdrawal qdUserWithdrawal = this.getById(m);
                QdUserWallet qdUserWallet = userWalletService.getByUserId(String.valueOf(qdUserWithdrawal.getUserId()));
                QdUserWallet wallet = new QdUserWallet();
                wallet.setId(qdUserWallet.getId());
                wallet.setWithdrawalEndWallet(qdUserWallet.getWithdrawalEndWallet().add(qdUserWithdrawal.getWithdrawalAmount()));
                wallet.setFrozenWallet(qdUserWallet.getFrozenWallet().subtract(qdUserWithdrawal.getWithdrawalAmount()));
                userWalletService.updateById(wallet);
                //插入日志
                QdUserWalletLog qdUserWalletLog = new QdUserWalletLog();
                qdUserWalletLog.setUserId(qdUserWithdrawal.getUserId());
                qdUserWalletLog.setChangeAmount(qdUserWithdrawal.getWithdrawalAmount());
                qdUserWalletLog.setType("4");
                qdUserWalletLog.setDetail("提现申请成功");
                walletLogService.save(qdUserWalletLog);
            });
        }else {
            //审核失败
            //余额从冻结恢复可提现余额
            Arrays.stream(strings).forEach(m->{
                QdUserWithdrawal qdUserWithdrawal = this.getById(m);
                QdUserWallet qdUserWallet = userWalletService.getByUserId(String.valueOf(qdUserWithdrawal.getUserId()));
                QdUserWallet wallet = new QdUserWallet();
                wallet.setId(qdUserWallet.getId());
                wallet.setWithdrawalWallet(qdUserWallet.getWithdrawalWallet().add(qdUserWithdrawal.getWithdrawalAmount()));
                wallet.setFrozenWallet(qdUserWallet.getFrozenWallet().subtract(qdUserWithdrawal.getWithdrawalAmount()));
                userWalletService.updateById(wallet);
                //插入日志
                QdUserWalletLog qdUserWalletLog = new QdUserWalletLog();
                qdUserWalletLog.setUserId(qdUserWithdrawal.getUserId());
                qdUserWalletLog.setChangeAmount(qdUserWithdrawal.getWithdrawalAmount());
                qdUserWalletLog.setType("3");
                qdUserWalletLog.setDetail("提现申请驳回");
                walletLogService.save(qdUserWalletLog);
            });
        }
        //修改用户提现记录状态
        return this.updateBatchById(Arrays.stream(strings).map(m -> {
            QdUserWithdrawal qdUserWithdrawal = new QdUserWithdrawal();
            qdUserWithdrawal.setId(Long.valueOf(m));
            qdUserWithdrawal.setStatus(dto.getStatus());
            return qdUserWithdrawal;
        }).collect(Collectors.toList()));
    }
}
